import org.grailsext.util.Utils
import org.apache.commons.lang.StringUtils
import org.apache.commons.collections.SetUtils

class AnswerController extends BaseController{

	def beforeInterceptor = [action:this.&auth]

    static allowedMethods = [save: "POST", update: "POST", delete: "POST"]

    def index = {
        redirect(action: "list", params: params)
    }

    def list = {
        params.max = Math.min(params.max ? params.int('max') : 10, 100)
		println session.userName
		def answerListByUser = session.userId?Answer.findAllByUserId(session.userName):null
        [answerInstanceList: answerListByUser, answerInstanceTotal: answerListByUser.size()]
    }

	// Make voting
	def makeVote = {
		println params
		println "Questionnaire ID: ${params.qstireId}"
		params.questions = Questionnaire.findById(params.qstireId)?.questions
		// Find existed answer first
		Question q = Question.get(params.questionId)
        def answerInstance = new Answer()
		answerInstance.question = q
		println Answer.findByUserIdAndQuestion(session.userName, q)
		if(Answer.findByUserIdAndQuestion(session.userName, q) != null){
			return [question: q]
		}

        answerInstance.properties = params
		
		if(answerInstance.question){
			return [answerInstance: answerInstance, question: q]
		} else {
			redirect(action: "list")
		}
	}

	// Statistics of voting
	def stat = {
		// Query condition

		// Stat result：
		//   Map(questionId, (Map(departmentId, Map(answerOrder, Map(questionItemId, count))))
		Map result = new HashMap()
		for(Question q: Question.list()){
			if(q.type!= "multi_select"){
				continue
			}
			// For each question
			println "${q.id} - ${q.content}"
			// find all departments Map(departmentName, [departmentName])
			Map departments = new HashMap()
			for(User u: User.list()){
				if(u.department == "系统管理员"){
					continue
				}
				departments.put(u.department, u.department)
			}
			println "Department: ${departments.keySet()}"
			Map rsltUserAnswers = new HashMap()

			for(String dep : departments.keySet()) {
				println "Department: ${dep}"
				Map rsltSubAnswers = new HashMap()
				// 所有某部门选择的问题（Question）的答案（Answer）
				def subAnswers = Answer.findAllByDepartmentAndQuestion(dep, q)
				// 按照答案选项的优先级
				for(int i =0; i < q.multiSelect; i++) {
					Map rsltAnswerItems = rsltSubAnswers.get(i)
					if(rsltAnswerItems == null) {
						rsltAnswerItems = new HashMap()//每一个优先级一个Map(questionItemId, number)
					}
					// 这个部门的每个回答
					for(Answer a: subAnswers) {
						println a
						// 答案每个的选项
						for(AnswerItem ai: a.answerItems) {
							//按照顺序来
							if(ai.answerOrder == i+1) {
								println ai.questionItemId
								println rsltAnswerItems.get(ai.questionItemId)
								int count = rsltAnswerItems.get(ai.questionItemId)?:0
								rsltAnswerItems.put(ai.questionItemId, ++count)//递增
							}
						}
					}
					rsltAnswerItems.put("totalOfDepartment", subAnswers.size())
					rsltSubAnswers.put(i, rsltAnswerItems)
				}
				rsltUserAnswers.put(dep, rsltSubAnswers)
			}
			//某个问题总的统计
			Map rsltSubAnswers = new HashMap()
			//重复类似代码.开始
			def subAnswers = Answer.findAllByQuestion(q)
			for(int i =0; i < q.multiSelect; i++) {
				Map rsltAnswerItems = rsltSubAnswers.get(i)
				if(rsltAnswerItems == null) {
					rsltAnswerItems = new HashMap()//每一个优先级一个Map(questionItemId, number)
				}
				// 所有用户的每个回答
				for(Answer a: subAnswers) {
					println a
					// 答案每个的选项
					for(AnswerItem ai: a.answerItems) {
						//按照顺序来
						if(ai.answerOrder == i+1) {
							println ai.questionItemId
							println rsltAnswerItems.get(ai.questionItemId)
							int count = rsltAnswerItems.get(ai.questionItemId)?:0
							rsltAnswerItems.put(ai.questionItemId, ++count)//递增
						}
					}
				}
				rsltAnswerItems.put("totalOfDepartment", subAnswers.size())
				rsltSubAnswers.put(i, rsltAnswerItems)
			}
			//重复类似代码.结束
			rsltUserAnswers.put("Total", rsltSubAnswers)
			result.put(q.id, rsltUserAnswers)
		}

		println 'Statistics Result ----'
		for(Map rsltUserAnswers : result) {
			//			Question q = Question.findById(rsltUserAnswers.key)
			println "Question ID: ${rsltUserAnswers.key}"
			Map rsltSubAnswers = rsltUserAnswers.value
			for(Object subAnswers : rsltSubAnswers) {
				//				User u = User.findByUserName(subAnswers.key)
				println "User id: ${subAnswers.key}"
				//				println "${subAnswers.value}"
				for(Object rsltAnswerItems: subAnswers){
					println "${rsltAnswerItems.key} - ${rsltAnswerItems.value}"
					for(Object rsltAnswerItem: rsltAnswerItems.value) {
						println "Order: ${rsltAnswerItem.key} - ${rsltAnswerItem.value}"
					}
				}

			}
		}
		println '---- Statistics Result'
		params.max = Math.min(params.max ? params.int('max') : 20, 100)
		[answerInstanceList: result, answerInstanceTotal: result.size()]
	}

	def bytext = {
		// Result: Map(int questionId, Map(int userId, String answerText))
		Map result = new HashMap()
		for(Question q: Question.list()){
			if(q.type!= "answer"){
				continue
			}
			// For each question
			println "${q.id} - ${q.content}"
			Map rsltUserAnswers = new HashMap()
			for(Object dep : departmentMap) {
				String depName = dep.key
				def subAnswers = Answer.findAllByDepartmentAndQuestion(depName, q)
				if(subAnswers){
					List answerTextList = rsltUserAnswers.get(depName)
					if(answerTextList == null) {
						answerTextList = new ArrayList()
						rsltUserAnswers.put(depName, answerTextList)
					}
					for(Answer a: subAnswers){
						answerTextList.add(a.at.content)
						//					rsltUserAnswers.put(depName, a.at.content)
					}
				}
			}
			//			for(User u : User.list()) {
			//				// For each user(group)
			//				println "${u.userName} - ${u.firstName}"
			//				// 所有某User选择的问题（Question）的答案（Answer）
			//				def subAnswers = Answer.findAllByUserIdAndQuestion(u.userName, q)
			//				for(Answer a: subAnswers){
			//					rsltUserAnswers.put(u.userName, a.at.content)
			//				}
			//			}
			result.put(q.id, rsltUserAnswers)
		}
		params.max = Math.min(params.max ? params.int('max') : 20, 100)
		[answerInstanceList: result, answerInstanceTotal: result.size()]
	}

	//    def create = {
	//        def answerInstance = new Answer()
	//        answerInstance.properties = params
	//        return [answerInstance: answerInstance]
	//    }

	// 保存用户的问题答案并跳至下一题
	def save = {
		println "answer-save -->"
		def answerInstance = new Answer(params)
		println "params ${params}"
		Question q = Question.findById(params.questionId)
		answerInstance.question = q
		// 检查用户投票限制
		println "User: ${session.sessionId} ${session.sessionName}"
		User u = User.findById(session.userId?:1)
		println "user: ${u}"
		int answersCount = Answer.countByUserIdAndQuestion(u.userName, q)
		println "answersCount: ${answersCount}"
		if(answersCount >= u.maxAnswers) {
			flash.message = "你已经完成了这个问题了，请选择下一题"
			//			render(view: "makeVote", params: [qstireId:params.qstireId, questionId:params.questionId], model: [answerInstance: answerInstance])
			redirect(action: "makeVote", params:[qstireId: answerInstance.question.questionnaire.id, questionId: params.questionId])
			return 
		}

		//TODO
		answerInstance.userId = session.userName?:'admin'
		answerInstance.department = session.department?:'System Admin'
		answerInstance.userIp = request.getRemoteAddr()
		answerInstance.answerTime = Calendar.getInstance()

		if(q.type == "multi_select"){
			// 多选题
			def selectedAnswerItems = params.selectedAnswerItems
			println selectedAnswerItems
			if(Utils.containsItem(selectedAnswerItems, "null") || selectedAnswerItems.length < q.multiSelect){
				flash.message = "没有选择完，请继续选择"
				redirect(action: "makeVote", params:[qstireId: answerInstance.question.questionnaire.id, questionId: params.questionId])
				return
			} else if(Utils.containsEqual(selectedAnswerItems)){
				flash.message = "有重复的选择项，请重新选择"
				redirect(action: "makeVote", params:[qstireId: answerInstance.question.questionnaire.id, questionId: params.questionId])
				return
			} else {
				println selectedAnswerItems
				int order =1;
				for(sai in selectedAnswerItems) {
					def ai = new AnswerItem(answerOrder: order++, questionItemId: sai)
					answerInstance.addToAnswerItems(ai)
				}
				if(!StringUtils.isEmpty(params.answerText)) {
					answerInstance.at = new AnswerText(content: params.answerText)
				}
			}

		} else if(q.type == "answer")  {
			//问答题
			def answerText = params.answerText
			if(StringUtils.isEmpty(answerText)) {
				flash.message = "请回答问题"
				redirect(action: "makeVote", params:[qstireId: answerInstance.question.questionnaire.id, questionId: params.questionId])
				return 
			}
			AnswerText at = new AnswerText()
			at.content = answerText
			answerInstance.at = at
		}

		//		if (answerInstance.save(flush: true)) {
		if(saveEntity(answerInstance)) {
			//			flash.message = "${message(code: 'default.created.message', args: [message(code: 'answer.label', default: 'Answer'), answerInstance.id])}"
			flash.message = "问题${params.questionId}保存成功，请继续下一题"
			redirect(action: "makeVote", params:[qstireId: answerInstance.question.questionnaire.id, questionId: answerInstance.question.id + 1])
		}
		else {
			flash.message = "保存回答错误"
			redirect(action: "makeVote", params:[qstireId: answerInstance.question.questionnaire.id, questionId: params.questionId])
		}
		println "<-- answer-save"
	}

	def show = {
		def answerInstance = Answer.get(params.id)
		if (!answerInstance) {
			flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'answer.label', default: 'Answer'), params.id])}"
			redirect(action: "list")
		}
		else {
			[answerInstance: answerInstance]
		}
	}

	def edit = {
		def answerInstance = Answer.get(params.id)
		if (!answerInstance) {
			flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'answer.label', default: 'Answer'), params.id])}"
			redirect(action: "list")
		}
		else {
			return [answerInstance: answerInstance]
		}
	}

	def update = {
		def answerInstance = Answer.get(params.id)
		if (answerInstance) {
			if (params.version) {
				def version = params.version.toLong()
				if (answerInstance.version > version) {
					answerInstance.errors.rejectValue("version", "default.optimistic.locking.failure", [message(code: 'answer.label', default: 'Answer')] as Object[], "Another user has updated this Answer while you were editing")
					render(view: "edit", model: [answerInstance: answerInstance])
					return
				}
			}
			answerInstance.properties = params
			if (!answerInstance.hasErrors() && answerInstance.save(flush: true)) {
				flash.message = "${message(code: 'default.updated.message', args: [message(code: 'answer.label', default: 'Answer'), answerInstance.id])}"
				redirect(action: "show", id: answerInstance.id)
			}
			else {
				render(view: "edit", model: [answerInstance: answerInstance])
			}
		}
		else {
			flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'answer.label', default: 'Answer'), params.id])}"
			redirect(action: "list")
		}
	}

	def delete = {
		def answerInstance = Answer.get(params.id)
		if (answerInstance) {
			try {
				answerInstance.delete(flush: true)
				flash.message = "${message(code: 'default.deleted.message', args: [message(code: 'answer.label', default: 'Answer'), params.id])}"
				redirect(action: "list")
			}
			catch (org.springframework.dao.DataIntegrityViolationException e) {
				flash.message = "${message(code: 'default.not.deleted.message', args: [message(code: 'answer.label', default: 'Answer'), params.id])}"
				redirect(action: "show", id: params.id)
			}
		}
		else {
			flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'answer.label', default: 'Answer'), params.id])}"
			redirect(action: "list")
		}
	}
}
